שפרו את איכות הקוד בפרויקטי JavaScript באמצעות pre-commit hooks. למדו כיצד להגדיר וליישם שערי איכות קוד לפרויקטים נקיים וקלים יותר לתחזוקה.
שערי איכות קוד ב-JavaScript: שליטה בהגדרות Pre-commit Hooks
בעולם פיתוח התוכנה המתפתח ללא הרף, שמירה על איכות קוד גבוהה היא בעלת חשיבות עליונה. קוד נקי, מעוצב היטב וללא באגים לא רק מפחית את עלויות התחזוקה, אלא גם מטפח שיתוף פעולה ומאיץ את מחזורי הפיתוח. טכניקה רבת עוצמה לאכיפת איכות קוד היא יישום של שערי איכות קוד באמצעות pre-commit hooks. מאמר זה מספק מדריך מקיף להגדרת pre-commit hooks עבור פרויקטי JavaScript, ומאפשר לכם להפוך בדיקות איכות קוד לאוטומטיות עוד לפני שהקוד מגיע למאגר שלכם.
מהם Pre-commit Hooks?
Git hooks הם סקריפטים ש-Git מריץ לפני או אחרי אירועים כמו commit, push, ו-receive. Pre-commit hooks, באופן ספציפי, רצים לפני ש-commit מסתיים. הם מציעים הזדמנות מכרעת לבדוק את השינויים שעומדים להיכנס ומונעים קומיטים שאינם עומדים בתקני איכות שהוגדרו מראש. חשבו עליהם כשומרי סף שמונעים מקוד באיכות נמוכה להיכנס לבסיס הקוד שלכם.
למה להשתמש ב-Pre-commit Hooks לאיכות קוד JavaScript?
- זיהוי שגיאות מוקדם: Pre-commit hooks תופסים בעיות איכות קוד בשלב מוקדם בתהליך הפיתוח, ומונעים מהן להתפשט הלאה. זה הרבה יותר יעיל מאשר לגלות בעיות במהלך סקירות קוד או, גרוע מכך, בפרודקשן.
- עיצוב קוד אוטומטי: הבטיחו סגנון קוד עקבי בכל הצוות והפרויקט. עיצוב אוטומטי מונע ויכוחים סגנוניים ותורם לבסיס קוד קריא יותר.
- הפחתת הנטל בסקירות קוד: על ידי אכיפה אוטומטית של תקני קידוד, pre-commit hooks מפחיתים את הנטל על סוקרי הקוד, ומאפשרים להם להתמקד בהחלטות ארכיטקטוניות ובלוגיקה מורכבת.
- יכולת תחזוקה משופרת של הקוד: בסיס קוד עקבי ואיכותי קל יותר לתחזוקה ולפיתוח לאורך זמן.
- אכיפת עקביות: הם מבטיחים שכל הקוד תואם לתקני הפרויקט, ללא קשר למפתח שכתב אותו. זה חשוב במיוחד בצוותים מבוזרים העובדים ממיקומים שונים – למשל, לונדון, טוקיו ובואנוס איירס – שבהם סגנונות הקידוד האישיים עשויים להשתנות.
כלים מרכזיים לאיכות קוד JavaScript
מספר כלים משמשים בדרך כלל בשילוב עם pre-commit hooks לאוטומציה של בדיקות איכות קוד JavaScript:
- ESLint: לינטר (linter) JavaScript חזק שמזהה שגיאות פוטנציאליות, אוכף סגנונות קידוד ועוזר לשפר את קריאות הקוד. הוא תומך במגוון רחב של כללים וניתן להתאמה אישית גבוהה.
- Prettier: כלי לעיצוב קוד (formatter) דעתני שמעצב קוד באופן אוטומטי כדי שיתאים לסגנון עקבי. הוא תומך ב-JavaScript, TypeScript, JSX ושפות רבות אחרות.
- Husky: כלי המקל על ניהול Git hooks. הוא מאפשר להגדיר סקריפטים שיבוצעו בשלבים שונים של תהליך העבודה ב-Git.
- lint-staged: כלי שמריץ לינטרים ופורמטרים רק על קבצים שנמצאים ב-staging, מה שמאיץ משמעותית את תהליך ה-pre-commit. זה מונע בדיקות מיותרות על קבצים שלא שונו.
הגדרת Pre-commit Hooks: מדריך צעד אחר צעד
להלן מדריך מפורט כיצד להגדיר pre-commit hooks עבור פרויקט ה-JavaScript שלכם באמצעות Husky ו-lint-staged:
שלב 1: התקנת תלויות
ראשית, התקינו את החבילות הנחוצות כתלויות פיתוח (development dependencies) באמצעות npm או yarn:
npm install --save-dev husky lint-staged eslint prettier
או, באמצעות yarn:
yarn add --dev husky lint-staged eslint prettier
שלב 2: אתחול Husky
Husky מפשט את תהליך ניהול ה-Git hooks. אתחלו אותו באמצעות הפקודה הבאה:
npx husky install
פעולה זו תיצור ספריית `.husky` בפרויקט שלכם, אשר תאחסן את ה-Git hooks שלכם.
שלב 3: הגדרת ה-Pre-commit Hook
הוסיפו pre-commit hook באמצעות Husky:
npx husky add .husky/pre-commit "npx lint-staged"
פקודה זו יוצרת קובץ `pre-commit` בספריית `.husky` ומוסיפה אליו את הפקודה `npx lint-staged`. זה אומר ל-Git להריץ את lint-staged לפני כל קומיט.
שלב 4: הגדרת lint-staged
lint-staged מאפשר לכם להריץ לינטרים ופורמטרים רק על הקבצים שב-staged, מה שמאיץ משמעותית את תהליך ה-pre-commit. צרו קובץ `lint-staged.config.js` (או `lint-staged.config.mjs` עבור מודולי ES) בשורש הפרויקט והגדירו אותו באופן הבא:
module.exports = {
'*.{js,jsx,ts,tsx}': ['eslint --fix', 'prettier --write'],
};
הגדרה זו אומרת ל-lint-staged להריץ את ESLint ו-Prettier על כל קבצי ה-JavaScript וה-TypeScript שב-staged. הדגל `--fix` ב-ESLint מתקן אוטומטית כל שגיאת לינטינג שניתן לתקן באופן אוטומטי, והדגל `--write` ב-Prettier מעצב את הקבצים ודורס אותם עם הקוד המעוצב.
לחלופין, ניתן להגדיר את התצורה ישירות בקובץ ה-`package.json` שלכם:
{
"lint-staged": {
"*.{js,jsx,ts,tsx}": [
"eslint --fix",
"prettier --write"
]
}
}
שלב 5: הגדרת ESLint
אם עדיין לא עשיתם זאת, הגדירו את ESLint עבור הפרויקט שלכם. ניתן ליצור קובץ תצורת ESLint באמצעות הפקודה הבאה:
npx eslint --init
פעולה זו תדריך אתכם בתהליך יצירת קובץ תצורת ESLint (`.eslintrc.js`, `.eslintrc.json`, או `.eslintrc.yml`) בהתבסס על דרישות הפרויקט שלכם. תוכלו לבחור מתוך מגוון תצורות מוגדרות מראש או ליצור כללים מותאמים אישית משלכם.
דוגמה לקובץ `.eslintrc.js`:
module.exports = {
env: {
browser: true,
es2021: true,
node: true
},
extends: [
'eslint:recommended',
'plugin:react/recommended',
'plugin:@typescript-eslint/recommended',
'prettier'
],
parser: '@typescript-eslint/parser',
parserOptions: {
ecmaFeatures: {
jsx: true
},
ecmaVersion: 12,
sourceType: 'module'
},
plugins: [
'react',
'@typescript-eslint'
],
rules: {
'no-unused-vars': 'warn',
'react/prop-types': 'off'
}
};
תצורה זו מרחיבה את כללי ESLint המומלצים, כללי React המומלצים, כללי TypeScript המומלצים, ומשתלבת עם Prettier. היא גם מבטלת את הכלל `react/prop-types` ומגדירה את הכלל `no-unused-vars` כאזהרה.
שלב 6: הגדרת Prettier
הגדירו את Prettier על ידי יצירת קובץ `.prettierrc.js` (או `.prettierrc.json`, `.prettierrc.yml`, או `.prettierrc.toml`) בשורש הפרויקט. תוכלו להתאים אישית את אפשרויות העיצוב של Prettier כך שיתאימו להנחיות הסגנון של הפרויקט שלכם.
דוגמה לקובץ `.prettierrc.js`:
module.exports = {
semi: false,
trailingComma: 'all',
singleQuote: true,
printWidth: 120,
tabWidth: 2
};
תצורה זו מגדירה את Prettier להשתמש בגרשיים בודדים, ללא נקודה-פסיק, פסיק נגרר (trailing comma) בכל המקרים, רוחב הדפסה של 120 תווים, ורוחב טאב של 2 רווחים.
לחלופין, ניתן להגדיר את תצורת Prettier בתוך `package.json`:
{
"prettier": {
"semi": false,
"trailingComma": "all",
"singleQuote": true,
"printWidth": 120,
"tabWidth": 2
}
}
שלב 7: בדקו את התצורה שלכם
כדי לבדוק את התצורה שלכם, הכניסו כמה שינויים ל-stage ונסו לבצע קומיט. לדוגמה:
git add .
git commit -m "Test pre-commit hook"
אם יש בעיות לינטינג או עיצוב, ESLint ו-Prettier יתקנו אותן אוטומטית (במידת האפשר) או ידווחו על שגיאות. אם מדווחות שגיאות, הקומיט יבוטל, מה שיאפשר לכם לתקן את הבעיות לפני ביצוע קומיט נוסף.
אפשרויות תצורה מתקדמות
שימוש בלינטרים ופורמטרים שונים
ניתן לשלב בקלות לינטרים ופורמטרים אחרים בתצורת ה-pre-commit hook שלכם. לדוגמה, ניתן להשתמש ב-Stylelint לבדיקת קבצי CSS או SASS:
npm install --save-dev stylelint stylelint-config-standard
לאחר מכן, עדכנו את קובץ `lint-staged.config.js` שלכם כדי שיכלול את Stylelint:
module.exports = {
'*.{js,jsx,ts,tsx}': ['eslint --fix', 'prettier --write'],
'*.{css,scss}': ['stylelint --fix'],
};
הרצת בדיקות לפני קומיט
ניתן גם להריץ את בדיקות היחידה (unit tests) שלכם כחלק מה-pre-commit hook. זה עוזר להבטיח שהקוד שלכם עובד כראוי לפני שהוא נכנס למאגר. בהנחה שאתם משתמשים ב-Jest:
npm install --save-dev jest
עדכנו את קובץ `lint-staged.config.js` שלכם כדי שיכלול את פקודת הבדיקה:
module.exports = {
'*.{js,jsx,ts,tsx}': ['eslint --fix', 'prettier --write', 'jest --findRelatedTests'],
'*.{css,scss}': ['stylelint --fix'],
};
הדגל `--findRelatedTests` אומר ל-Jest להריץ רק בדיקות הקשורות לקבצים שהשתנו, מה שמאיץ משמעותית את התהליך.
דילוג על Pre-commit Hooks
במקרים מסוימים, ייתכן שתרצו לדלג זמנית על ה-pre-commit hooks. ניתן לעשות זאת באמצעות הדגל `--no-verify` עם פקודת `git commit`:
git commit --no-verify -m "Commit message"
עם זאת, בדרך כלל מומלץ להימנע מדילוג על ההוקים אלא אם כן זה הכרחי לחלוטין, מכיוון שהם ממלאים תפקיד חיוני בשמירה על איכות הקוד.
פתרון בעיות נפוצות
- ההוקים לא רצים: ודאו ש-Husky מותקן ומאותחל כראוי, ושספריית `.husky` קיימת בשורש הפרויקט. ודאו גם שהקובץ `pre-commit` בספריית `.husky` הוא קובץ הרצה (executable).
- שגיאות לינטינג לא מתוקנות: ודאו שנעשה שימוש בדגל `--fix` עם ESLint, ושתצורת ה-ESLint שלכם מוגדרת לתקן אוטומטית סוגים מסוימים של שגיאות.
- Prettier לא מעצב קבצים: ודאו שנעשה שימוש בדגל `--write` עם Prettier, ושתצורת ה-Prettier שלכם מוגדרת כראוי.
- Pre-commit hooks איטיים: השתמשו ב-lint-staged כדי להריץ לינטרים ופורמטרים רק על קבצים שב-staged. שקלו גם למטב את תצורות ה-ESLint וה-Prettier שלכם כדי למזער את מספר הכללים וההגדרות שנבדקים.
- תצורות מתנגשות: ודאו שתצורות ה-ESLint וה-Prettier שלכם אינן מתנגשות זו בזו. אם כן, ייתכן שתצטרכו להתאים אחת מהתצורות או את שתיהן כדי לפתור את ההתנגשויות. שקלו להשתמש בתצורה משותפת כמו `eslint-config-prettier` ו-`eslint-plugin-prettier` כדי למנוע התנגשויות.
שיטות עבודה מומלצות ל-Pre-commit Hooks
- שמרו על הוקים מהירים: הוקים איטיים יכולים להשפיע באופן משמעותי על פרודוקטיביות המפתחים. השתמשו ב-lint-staged כדי לעבד רק קבצים שב-staged ומטבו את תצורות הלינטר והפורמטר שלכם.
- ספקו הודעות שגיאה ברורות: כאשר הוק נכשל, ספקו הודעות שגיאה ברורות ואינפורמטיביות כדי להדריך את המפתחים כיצד לתקן את הבעיות.
- אוטומציה ככל האפשר: הפכו את עיצוב הקוד והלינטינג לאוטומטיים כדי למזער מאמץ ידני ולהבטיח עקביות.
- הדריכו את הצוות שלכם: ודאו שכל חברי הצוות מבינים את מטרת ה-pre-commit hooks וכיצד להשתמש בהם ביעילות.
- השתמשו בתצורה עקבית: שמרו על תצורה עקבית עבור ESLint, Prettier וכלים אחרים ברחבי הפרויקט. זה יעזור להבטיח שכל הקוד מעוצב ועובר לינטינג באותו אופן. שקלו להשתמש בחבילת תצורה משותפת שניתן להתקין ולעדכן בקלות בין מספר פרויקטים.
- בדקו את ההוקים שלכם: בדקו באופן קבוע את ה-pre-commit hooks שלכם כדי לוודא שהם פועלים כראוי ושהם לא גורמים לבעיות בלתי צפויות.
שיקולים גלובליים
בעבודה בצוותים מבוזרים גלובלית, שקלו את הדברים הבאים:
- גרסאות כלים עקביות: ודאו שכל חברי הצוות משתמשים באותן גרסאות של ESLint, Prettier, Husky ו-lint-staged. ניתן להשיג זאת על ידי ציון הגרסאות בקובץ `package.json` שלכם ושימוש במנהל חבילות כמו npm או yarn להתקנת התלויות.
- תאימות בין פלטפורמות: בדקו את ה-pre-commit hooks שלכם על מערכות הפעלה שונות (Windows, macOS, Linux) כדי לוודא שהם פועלים כראוי בכל הפלטפורמות. השתמשו בכלים ופקודות חוצי-פלטפורמות במידת האפשר.
- הבדלי אזורי זמן: היו מודעים להבדלי אזורי זמן בעת תקשורת עם חברי צוות לגבי בעיות ב-pre-commit hooks. ספקו הוראות ודוגמאות ברורות כדי לעזור להם לפתור את הבעיות במהירות.
- תמיכה בשפות: אם הפרויקט שלכם כולל עבודה עם מספר שפות, ודאו שה-pre-commit hooks שלכם תומכים בכל השפות המשמשות בפרויקט. ייתכן שתצטרכו להתקין לינטרים ופורמטרים נוספים עבור כל שפה.
סיכום
יישום pre-commit hooks הוא דרך יעילה לאכוף איכות קוד, לשפר את שיתוף הפעולה בצוות ולהפחית עלויות תחזוקה בפרויקטי JavaScript. על ידי שילוב כלים כמו ESLint, Prettier, Husky ו-lint-staged, ניתן להפוך את עיצוב הקוד, הלינטינג והבדיקות לאוטומטיים, ולהבטיח שרק קוד באיכות גבוהה נכנס למאגר שלכם. על ידי ביצוע השלבים המפורטים במדריך זה, תוכלו להקים שער איכות קוד חזק שיעזור לכם לבנות יישומי JavaScript נקיים, קלים יותר לתחזוקה ואמינים יותר. אמצו נוהג זה ושדרגו את תהליך הפיתוח של הצוות שלכם עוד היום.